package cn.ac.big.bigd.service;

import cn.ac.big.bigd.dao.*;
import cn.ac.big.bigd.gsa.service.GsaServive;
import cn.ac.big.bigd.model.User;
import cn.ac.big.bigd.model.generate.*;
import cn.ac.big.bigd.model.submit.*;
import cn.ac.big.bigd.util.TabUtil;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.io.File;
import java.util.Date;
import java.util.List;
import java.util.Map;

/**
 * @Author wangfan
 * @Date 2016/11/29 15:53
 */

@Service
public class StatsService {


    @Autowired
    GsaServive gsaServive;
    @Autowired
    SubmissionDao submissionDao;
    @Autowired
    NewAssemblyDao newAssemblyDao;
    @Autowired
    NewGenomeDao newGenomeDao;
    @Autowired
    NewAnnotationDao newAnnotationDao;

    @Autowired
    NewAnnotationDetailDao newAnnotationDetailDao;
    @Autowired
    NewStatisticsDao newStatisticsDao;

    /*保存统计信息，逻辑*/
    public void saveStats(Submission submission, String savePath) throws Exception {
        Map map = gsaServive.findBySampleWithResult(submission.getGeneralInfo().getBioSampleAccession());
        long taxonId = Long.valueOf(map.get("taxonId").toString());//通过speciesCode判定genome是否存在
        NewAssembly newAssembly = newAssemblyDao.findByAccession(submission.getAccession());
        NewGenome newGenome;
        if (null != newAssembly) {//如果存在assembly，则一定存在genome更新
            newGenome = newAssembly.getNewGenome();
        } else {
            newAssembly = new NewAssembly();
            newGenome = newGenomeDao.findByTaxonId(taxonId);
            if (null == newGenome) {
                newGenome = new NewGenome();
            }
        }
        newGenome.setSource("GWH");
        newGenome.setCreatedAt(new Date());
        newGenome.setScientificName(map.get("scientificName").toString());
        newGenome.setCommonName(map.get("commonName").toString());
        newGenome.setSamplePicture("");
        newGenome.setTaxonId(taxonId);
        newGenome.setStatus(0);
        newGenome = newGenomeDao.save(newGenome);
        newAssembly.setSource("GWH");
        newAssembly.setSampleName(map.get("sampleName").toString());
        newAssembly.setBioProjectAccession(submission.getGeneralInfo().getBioProjectAccession());
        newAssembly.setBioSampleAccession(submission.getGeneralInfo().getBioSampleAccession());
        newAssembly.setAccession(submission.getAccession());

        if (submission.getGeneralInfo().isUpdateSubmission()) {
            if (submission.getGeneralInfo().getGenomeAccession().startsWith("GWH")) {
                newAssembly.setVersion("v1");//
            } else {
                newAssembly.setVersion("v0");
            }
        }
        //什么情况下修改版本号
        ObjectMapper mapper = new ObjectMapper();
        newAssembly.setLab(submission.getSubmitter().getDepartment() + "," + submission.getSubmitter().getOrganization());
        List<Author> authors = submission.getReference().getAuthorList();

        String s = "";
        for (int i = 0; i < authors.size(); i++) {
            Author author = authors.get(i);
            if (i == authors.size() - 1) {
                s = s + author.getFirstName() + " " + author.getLastName() + "   " + author.getEmail() + "";
            } else {
                s = s + author.getFirstName() + " " + author.getLastName() + "   " + author.getEmail() + "<br>";
            }

        }
//        newAssembly.setContacts(mapper.writeValueAsString(submission.getReference().getAuthorList()));
        newAssembly.setContacts(s);


        List<TechnologyAndCoverage> technologyAndCoverages = submission.getGeneralInfo().getTechnologyAndCoverageList();
        s = "";
        for (int i = 0; i < technologyAndCoverages.size(); i++) {
            TechnologyAndCoverage technologyAndCoverage = technologyAndCoverages.get(i);
            String name = technologyAndCoverage.getTechnology().getName();
            if (name.equals("Other")) {
                name = technologyAndCoverage.getOtherTechnology();
            }
            if (i == technologyAndCoverages.size() - 1) {

                s = s + name + " " + technologyAndCoverage.getGenomeCoverage() + "";
            } else {
                s = s + name + " " + technologyAndCoverage.getGenomeCoverage() + "<br>";
            }


        }


//        newAssembly.setTechnologyAndCoverage(mapper.writeValueAsString(submission.getGeneralInfo().getTechnologyAndCoverageList()));
        newAssembly.setTechnologyAndCoverage(s);


        List<AssemblyMethodVersion> assemblyMethodVersions = submission.getGeneralInfo().getAssemblyMethodVersion();
        s = "";
        for (int i = 0; i < assemblyMethodVersions.size(); i++) {
            AssemblyMethodVersion assemblyMethodVersion = assemblyMethodVersions.get(i);
            String name = assemblyMethodVersion.getAssemblyMethod().getName();
            if (name.equals("Other")) {
                name = assemblyMethodVersion.getOtherAssemblyMethod();
            }
            if (i == assemblyMethodVersions.size() - 1) {

                s = s + name + " " + assemblyMethodVersion.getMethodversion() + "";
            } else {
                s = s + name + " " + assemblyMethodVersion.getMethodversion() + "<br>";
            }


        }


//        newAssembly.setAssemblymethods(mapper.writeValueAsString(submission.getGeneralInfo().getAssemblyMethodVersion()));
        newAssembly.setAssemblymethods(s);


        newAssembly.setCountry(submission.getSubmitter().getCountry().getCountryName());
        newAssembly.setSampleSource("GWH");
        newAssembly.setQc(submission.getFiles().isCheckProcesses());
        if (!newAssembly.isReleased()) {
            newAssembly.setReleasedAt(submission.getGeneralInfo().getReleaseDate());
        }

        newAssembly.setAssemblyLevel(submission.getFiles().getAssemblyLevel());
//            int re =submission.getGeneralInfo().getRepersent();
        newAssembly.setGenomeRepresentation(submission.getGeneralInfo().getRepersent() + "");
        if (null == submission.getGeneralInfo().getGenomeComprise()) {

        } else {
            if (null != submission.getGeneralInfo().getGenomeComprise().getChromosome()) {
                newAssembly.setChr(submission.getGeneralInfo().getGenomeComprise().getChromosome());
            }
            if (null != submission.getGeneralInfo().getGenomeComprise().getPloidy()) {
                newAssembly.setCopyNumber(submission.getGeneralInfo().getGenomeComprise().getPloidy());
            }
            if (null != submission.getGeneralInfo().getGenomeComprise().getPlasmid()) {
                newAssembly.setPlasmidNum(submission.getGeneralInfo().getGenomeComprise().getPlasmid());
            }
            if (null != submission.getGeneralInfo().getGenomeComprise().getMithochondria()) {
                newAssembly.setMitochondrion(submission.getGeneralInfo().getGenomeComprise().getMithochondria() == 1);
            }
            if (null != submission.getGeneralInfo().getGenomeComprise().getChloroplast()) {
                newAssembly.setChloroplast(submission.getGeneralInfo().getGenomeComprise().getChloroplast() == 1);
            }
            if (null != submission.getGeneralInfo().getGenomeComprise().getOtherComprise()) {
                newAssembly.setOtherComponent(submission.getGeneralInfo().getGenomeComprise().getOtherComprise());
            }
        }

        newAssembly.setReadsAccession(submission.getGeneralInfo().getReadsAccession());
        newAssembly.setSupplementaryUrl("");


        s = "";

        if (!submission.getReference().getPublicationStatus().equals("unplished")) {
            List<ReferenceAuthor> referenceList = submission.getReference().getReferenceAuthorList();
            if (referenceList.size() > 0) {
                ReferenceAuthor author = referenceList.get(0);
                if (referenceList.size() > 1) {
                    s = s + "" + author.getFirstName() + " " + author.getLastName() + ", et al. ";

                } else {
                    s = s + "" + author.getFirstName() + " " + author.getLastName() + ". ";
                }
                s = s + "" + submission.getReference().getReferenceTitle() + ". ";
                s = s + "" + submission.getReference().getJournalTitle() + ". ";
                s = s + "" + submission.getReference().getYear();

                if (null != submission.getReference().getVolumn() && !submission.getReference().getVolumn().isEmpty()) {
                    s = s + ", " + submission.getReference().getVolumn();


                }
                if (null != submission.getReference().getIssue() && !submission.getReference().getIssue().isEmpty()) {
                    s = s + "(" + submission.getReference().getIssue() + ")";

                }

                if (null != submission.getReference().getPagesFrom() && !submission.getReference().getPagesFrom().isEmpty()) {
                    s = s + ": " + submission.getReference().getPagesFrom();
                    if (null != submission.getReference().getPagesTo() && !submission.getReference().getPagesTo().isEmpty()) {
                        s = s + "- " + submission.getReference().getPagesTo() + "";
                    }
                }
                s = s + ". ";

            } else {
                s = s + "-";
            }


        }else {
            s = s + "-";
        }

    /*    for (int i = 0; i < referenceList.size(); i++) {
            ReferenceAuthor author =referenceList.get(i);
            if(i==referenceList.size()-1){
                s= s+author.getFirstName()+" " +author.getLastName()+"   "+author.getEmail()+"";
            }else {
                s= s+author.getFirstName()+" " +author.getLastName()+"   "+author.getEmail()+"<br>";
            }




        }*/


//        newAssembly.setPapers(submission.getReference().getJournalTitle());
        newAssembly.setPapers(s);


        newAssembly.setDNA("");
        newAssembly.setRNA("");
        newAssembly.setGFF("");
        newAssembly.setProtein("");
        newAssembly.setAncestorAssemblyAccessions(submission.getGeneralInfo().getGenomeAccession());
        newAssembly.setNewGenome(newGenome);
        newAssembly.setName(submission.getGeneralInfo().getAssemblyName());
        newAssembly = newAssemblyDao.save(newAssembly);

        long vlue = newStatisticsDao.deleteByNewAssembly(newAssembly);
        vlue = newAnnotationDao.deleteByNewAssembly(newAssembly);
        vlue = newAnnotationDetailDao.deleteByNewAssembly(newAssembly);

        String wholeFilePath = savePath + submission.getAccession() + ".whole.stats";
        String detailFilePath = savePath + submission.getAccession() + ".detail.stats";
        String assemblyFilePath = savePath + submission.getAccession() + ".assembly.stats";
        if (new File(wholeFilePath).exists()) {
            List<NewAnnotation> newAnnotationList = TabUtil.getAnnotation(wholeFilePath, true);
            for (NewAnnotation newAnnotation : newAnnotationList) {
                newAnnotation.setNewAssembly(newAssembly);
                newAnnotationDao.save(newAnnotation);

            }
        }


        if (new File(detailFilePath).exists()) {
            List<NewAnnotationDetail> newAnnotationDetailList = TabUtil.getAnnotationDetail(detailFilePath, true);
            for (NewAnnotationDetail newAnnotationDetail : newAnnotationDetailList) {
                newAnnotationDetail.setNewAssembly(newAssembly);
                newAnnotationDetailDao.save(newAnnotationDetail);

            }
        }
        if (new File(assemblyFilePath).exists()) {
            List<NewStatistics> newStatisticsList = TabUtil.getStatistics(assemblyFilePath, false);
            for (NewStatistics newStatistics : newStatisticsList) {
                newStatistics.setNewAssembly(newAssembly);
                newStatisticsDao.save(newStatistics);

            }
        }
    }


}
